﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;

namespace Container.Library
{
    /// <summary>
    /// 注册管理类
    /// </summary>
    public class RegisterTypeManager
    {
        #region 变量

        /// <summary>
        /// 配置文件全路径
        /// </summary>
        private static string fileConfigFullName;

        /// <summary>
        /// 映射文件全路径
        /// </summary>
        private static string directoryFullPath;

        /// <summary>
        /// 集合
        /// </summary>
        private static Dictionary<string, RegisterType> instanceList;

        /// <summary>
        /// 侦听文件系统对象
        /// </summary>
        private static FileSystemWatcher sWatcher = new FileSystemWatcher()
        {
            NotifyFilter = NotifyFilters.CreationTime | NotifyFilters.LastWrite
        };

        /// <summary>
        /// 同步锁
        /// </summary>
        private static readonly object locker = new object();

        /// <summary>
        /// 配置文件的路径名
        /// </summary>
        private const string fileConfigPath = @"Config\Ioc\files.config.json";

        /// <summary>
        /// 文件存放的文件夹路径
        /// </summary>
        private const string directoryPath = @"Config\Ioc\";

        #endregion

        static RegisterTypeManager()
        {
            string rootDic = string.Empty;

            //try
            //{
            //    rootDic = AppContext.BaseDirectory;
            //}
            //catch
            //{
            //}

            rootDic = AppDomain.CurrentDomain.BaseDirectory;

            fileConfigFullName = string.Format("{0}{1}", rootDic, fileConfigPath);
            directoryFullPath = string.Format("{0}{1}", rootDic, directoryPath);

            sWatcher.Changed += (s, e) => { InitList(); };
            sWatcher.Path = Path.GetDirectoryName(directoryFullPath);
            InitList();
            sWatcher.EnableRaisingEvents = true;
        }

        /// <summary>
        /// 获取命令文件
        /// </summary>
        /// <returns>命令文件集合</returns>
        private static ConfigFiles GetDataCommandFileList()
        {
            return fileConfigFullName.FileToObject<ConfigFiles>();
        }

        /// <summary>
        /// 初始化命令集合
        /// </summary>
        private static void InitList()
        {
            lock (locker)
            {
                instanceList = new Dictionary<string, RegisterType>();

                // 获取命令集合
                var files = GetDataCommandFileList();

                RegisterTypes commands = null;

                foreach (var fileInstance in files.InstanceList)
                {
                    commands = $"{directoryFullPath}{fileInstance.FilePath}".FileToObject<RegisterTypes>();

                    if (commands == null) continue;

                    foreach (var commandInstance in commands.InstanceList)
                    {

                        var count = instanceList.Count(p => p.Key.Equals(commandInstance.InterfaceOrNamespace));
                        if (count > 1)
                        {
                            throw new AggregateException("已经加入相同的键:" + commandInstance.InterfaceOrNamespace);
                        }
                        else
                        {
                            instanceList.Add($"{commandInstance.InterfaceOrNamespace}:{commandInstance.ImplementOrProfile}", commandInstance);
                        }
                    }
                }
            }
        }

        /// <summary>
        /// 返回注入类信息
        /// </summary>
        /// <param name="name"></param>
        /// <returns></returns>
        public static Dictionary<string, RegisterType> GetTypesList()
        {
            return instanceList;
        }
    }
}
